﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Globalization;

namespace LastfmNet
{
    public class LastfmParameters
    {
        private SortedDictionary<string, string> parameters = null;

        public LastfmParameters()
        {
            parameters = new SortedDictionary<string, string>();
        }

        public LastfmParameters(string lastfmMethodName)
            : this()
        {
            this.Method = lastfmMethodName;
        }

        public void AddSessionKey(string sessionKey)
        {
            this["sk"] = sessionKey;
        }

        public void AddApiKey(string apiKey)
        {
            this["api_key"] = apiKey;
        }

        public void Sign(string lastfmSecret)
        {
            if (parameters.ContainsKey("api_sig")) parameters.Remove("api_sig");
            StringBuilder signatureBuilder = new StringBuilder();
            foreach (var item in parameters)
            {
                signatureBuilder.Append(item.Key.URLEncode());
                signatureBuilder.Append(item.Value.URLEncode());
            }
            signatureBuilder.Append(lastfmSecret);
            parameters.Add("api_sig", signatureBuilder.ToString().ToMD5());
        }

        public string Method
        {
            get
            {
                return this["method"];
            }
            set
            {
                this["method"] = value;
            }
        }

        public string this[string index]
        {
            get
            {
                if (parameters.ContainsKey(index)) return parameters[index];
                else return string.Empty;
            }
            set
            {
                if (parameters.ContainsKey(index)) parameters[index] = value;
                else parameters.Add(index, value);
            }
        }

        public byte[] ToByteArray()
        {
            return Encoding.UTF8.GetBytes(this.ToString());
        }

        public override string ToString()
        {
            StringBuilder urlQuery = new StringBuilder();
            foreach (var item in parameters)
            {
                urlQuery.Append(string.Format(CultureInfo.InvariantCulture, "&{0}={1}", item.Key.URLEncode(), item.Value.URLEncode()));
            }
            if (urlQuery.Length > 0 && urlQuery[0] == '&') return urlQuery.ToString().Substring(1);
            return urlQuery.ToString();
        }

        public override bool Equals(object obj)
        {
            if (obj == null || GetType() != obj.GetType())
            {
                return false;
            }
            LastfmParameters compareWith = obj as LastfmParameters;
            return this.parameters.Equals(compareWith.parameters);
        }

        public override int GetHashCode()
        {
            return parameters.GetHashCode();
        }
    }
}
